/*
 * Copyright 2010 Christoph Widulle (christoph.widulle@googlemail.com)
 *
 * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the
 * License. You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS"
 * BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language
 * governing permissions and limitations under the License.
 */



package com.android1.amarena2d.nodes.behavior.delegates;

import com.android1.amarena2d.commons.collections.FixedSizeArray;
import com.android1.amarena2d.engine.Config;
import com.android1.amarena2d.engine.EngineObject;
import com.android1.amarena2d.engine.TickTimer;
import com.android1.amarena2d.engine.Timer;
import com.android1.amarena2d.nodes.LifecycleObject;

public class TimerDelegateImpl extends EngineObject implements TimerDelegate {


    protected LifecycleObject owner;

    protected TickTimer tickTimer;
    //handling timer scheduled by this entity
    protected FixedSizeArray<Timer> targetsTimer;


    public TimerDelegateImpl(LifecycleObject owner) {
        this.owner = owner;
    }

      /**
     * Timer you schedule by this LifecycleObject, will automaticly be enabled/disabled on enter/exit.
     * Recycleable will be set to false, so we don't get into trouble.
     *
     * @param timer
     */
    public void schedule(final Timer timer) {
        ensureTimerPool();
        timer.setRecycleable(false);
        targetsTimer.add(timer);
        if (owner.isActive() && owner.isPlaying())
            engine.getScheduler().schedule(timer);
    }

    /**
     * Unschedule a timer you registered before by this LifecycleObject.
     * Timer will not be recycled because #schedule has set recycleable to false.
     *
     * @param timer
     */
    public void unschedule(final Timer timer) {
        if (targetsTimer != null) {
            targetsTimer.remove(timer);
            engine.getScheduler().unschedule(timer);
        }
    }

    public void pauseTimer() {
        if (targetsTimer != null) {
            final int s = targetsTimer.getCount();
            for (int i = 0; i < s; i++) {
                Timer t = targetsTimer.get(i);
                engine.getScheduler().unschedule(t);
            }
        }
    }

    public void resumeTimer() {
        if (targetsTimer != null) {
            final int s = targetsTimer.getCount();
            for (int i = 0; i < s; i++) {
                Timer t = targetsTimer.get(i);
                engine.getScheduler().schedule(t);
            }
        }
    }

    private void ensureTimerPool() {
        if (targetsTimer == null)
            targetsTimer = new FixedSizeArray<Timer>(engine.getConfig().get(Config.TIMER_MAX_BY_LIFECYCLE_OBJECT));
    }

    public TickTimer scheduleForTick() {
       return  scheduleForTick(0.0F);
    }

    public TickTimer scheduleForTick(final float interval) {
        if (tickTimer == null || tickTimer.getInterval() != interval) {
            if (tickTimer != null) {
                unschedule(tickTimer);
            }
            tickTimer = TickTimer.obtain(owner, interval);
            schedule(tickTimer);
        }
        return tickTimer;
    }

    public void unscheduleTickTimer() {
        if (tickTimer != null) {
            unschedule(tickTimer);
            tickTimer = null;
        }
    }

    public TickTimer getTickTimer() {
        return tickTimer;
    }
}